#!/usr/bin/env python3
"""
脚本名称：ch47_exe.py
功能描述： 演示线程的同步，通过银行存款和取款的案例来了解锁的使用场景,使用 with 语句管理锁(推荐)
作者：Gavin
创建日期：2025-05-22
版本：1.0
依赖库：无
使用方法： python ch47_exe.py
"""

import threading
import time

# 共享资源
shared_data = 0


class BankAccountThread(threading.Thread):
    def __init__(self, thread_name, operation, amount):
        threading.Thread.__init__(self)
        self.thread_name = thread_name
        self.operation = operation  # 'deposit' 或 'withdraw'
        self.amount = amount

    def run(self):
        print(f"{self.thread_name} 开始执行...")

        # 获取锁
        with account_lock:
            print(f"{self.thread_name} 获取了账户锁")
            global shared_data
            if self.operation == 'deposit':
                print(f"{self.thread_name} 存款前余额: {shared_data}")
                shared_data += self.amount
                print(f"{self.thread_name} 存入 {self.amount}, 新余额: {shared_data}")
            else:
                print(f"{self.thread_name} 取款前余额: {shared_data}")
                if shared_data >= self.amount:
                    shared_data -= self.amount
                    print(f"{self.thread_name} 取出 {self.amount}, 新余额: {shared_data}")
                else:
                    print(f"{self.thread_name} 余额不足!")
            print(f"{self.thread_name} 释放了账户锁\n")


# 创建锁对象
account_lock = threading.Lock()

# 创建线程
deposit_thread = BankAccountThread("存款线程", 'deposit', 100)
withdraw_thread = BankAccountThread("取款线程", 'withdraw', 50)

# 启动线程
deposit_thread.start()
time.sleep(0.1)  # 确保存款线程先获取锁
withdraw_thread.start()

# 等待线程完成
deposit_thread.join()
withdraw_thread.join()

print(f"最终账户余额: {shared_data}")
print("主线程退出")
